package cn.ekuma.rabbit;

import java.util.HashMap;
import java.util.List;

import cn.ekuma.rabbit.imp.ConfigModel;
import cn.ekuma.rabbit.spi.I_Model;
import cn.ekuma.security.bean.I_Role;

import com.openbravo.data.basic.BasicException;
import com.openbravo.data.loader.I_Session;
import com.openbravo.pos.base.AppProperties;

import net.xeoh.plugins.base.PluginManager;

public class ModelManager {
	PluginManager pmf;
	
	I_Session s;
	
	ConfigModel configModel;
	
	HashMap<String,I_Model> models=new HashMap<String,I_Model>();
	HashMap<String,List<I_Model>> commandModelCache=new HashMap<String,List<I_Model>>();
	
	I_Role loginRole;
	
	public ModelManager(PluginManager pmf,AppProperties properties) {
		super();
		this.pmf = pmf;
		configModel=new ConfigModel(properties);
		models.put(configModel.getModelName(), configModel);
	}
	

	public  PluginManager getPluginManager(){
		return pmf;
	}
	
	public ConfigModel getConfigModel() {
		return configModel;
	}


	public void setSession(I_Session s) {
		this.s = s;
	}

	public I_Session getSession(){
		return s;
	}
	
	public I_Model getModelByName(String name){
		I_Model mode=models.get(name);
		if(mode==null){
			Class c;
			try {
				c = Class.forName(name);
				if(isInterface(c,I_Model.class.getName())){
					mode=(I_Model) c.newInstance();
					List<String> des=mode.getModelDependents();
					if(des!=null)
						for(String de:des){
							I_Model mode1=getModelByName(de);
							if(mode1==null)
								return null;
						}
					addModel(mode);
				}
			} catch (ClassNotFoundException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			} catch (InstantiationException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			} catch (IllegalAccessException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			} catch (BasicException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
			
		}
		
		return mode;
	}
	
	public void addModel(I_Model model) throws BasicException{
		System.out.println("load model:"+model.getModelName());
		models.put(model.getModelName(), model);
		model.init(this);
		if(loginRole!=null&&model.getModelSecurityManager()!=null){
			model.getModelSecurityManager().init(loginRole);
		}
	}
	
	
	 public boolean isInterface(Class c, String szInterface)
     {
             Class[] face = c.getInterfaces();
             for (int i = 0, j = face.length; i < j; i++) 
             {
                     if(face[i].getName().equals(szInterface))
                     {
                             return true;
                     }
                     else
                     { 
                             Class[] face1 = face[i].getInterfaces();
                             for(int x = 0; x < face1.length; x++)
                             {
                                     if(face1[x].getName().equals(szInterface))
                                     {
                                             return true;
                                     }
                                     else if(isInterface(face1[x], szInterface))
                                     {
                                             return true;
                                     }
                             }
                     }
             }
             if (null != c.getSuperclass())
             {
                     return isInterface(c.getSuperclass(), szInterface);
             }
             return false;
     }

	public I_Role getLoginRole() {
		return loginRole;
	}

	public void setLoginRole(I_Role loginRole) {
		this.loginRole = loginRole;	
		for(I_Model model:models.values())
			if(loginRole!=null&&model.getModelSecurityManager()!=null){
				System.out.println("init mode security:"+model.getModelName());
				model.getModelSecurityManager().init(loginRole);
			}
	}	 
	 
}
